package com.thirdgroup.dao.base;

import com.thirdgroup.utils.DruidLocalUtil;
import org.apache.commons.dbutils.QueryRunner;
import org.apache.commons.dbutils.handlers.BeanHandler;
import org.apache.commons.dbutils.handlers.BeanListHandler;
import org.apache.commons.dbutils.handlers.ScalarHandler;

import java.lang.reflect.ParameterizedType;
import java.lang.reflect.Type;
import java.sql.Connection;
import java.sql.SQLException;
import java.util.List;

/**
 * @BelongsProject: LearnMySQL
 * @BelongsPackage: com.zys.DAO
 * @Author: ZYS
 * @CreateTime: 2024-04-09  18:58
 * @Description: TODO
 */
public abstract class BaseDAO <T> implements DAO<T>{

    private final QueryRunner  queryRunner = new QueryRunner();
    private Class<T> clazz = null;

    public BaseDAO() {
        Type genericSuperclass = this.getClass().getGenericSuperclass();
        ParameterizedType parameterizedType = (ParameterizedType) genericSuperclass;
        Type[] actualTypeArguments = parameterizedType.getActualTypeArguments();
        clazz = (Class<T>) actualTypeArguments[0];
    }


    @Override
    public int executeSQL( String sql, Object... args) {
        Connection connection = DruidLocalUtil.getConnection();
        int rows = 0;
        try {
             rows = queryRunner.update(connection, sql, args);
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }finally {
            DruidLocalUtil.closeConnection(connection);
        }
        return rows;
    }

    @Override
    public T findOne(String sql, Object... args) {
        Connection connection = DruidLocalUtil.getConnection();
        T queryResult = null;
        try {
            queryResult = queryRunner.query(connection, sql, new BeanHandler<>(clazz), args);
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }finally {
            DruidLocalUtil.closeConnection(connection);
        }
        return queryResult;
    }

    @Override
    public List<T> findAll( String sql, Object... args) {
        Connection connection = DruidLocalUtil.getConnection();
        List<T> queryResult = null;
        try {
            queryResult = queryRunner.query(connection, sql, new BeanListHandler<>(clazz), args);
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }finally {
            DruidLocalUtil.closeConnection(connection);
        }
        return queryResult;
    }

    @Override
    public Object getValue( String sql, Object... args) {
        Connection connection = DruidLocalUtil.getConnection();
        Object queryResult = null;
        try {
            queryResult = queryRunner.query(connection, sql, new ScalarHandler<>(), args);
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }
        return queryResult;
    }



}
